package prototype.clone;

import Singleton.HungrySingleton;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.Date;

/**
 * @Author: 蔡翔
 * @Date: 2019/12/7 13:27
 * @Version 1.0
 */
public class Test {
    /*
    // normal 类型
    public static void main(String[] args) throws CloneNotSupportedException {
        Date birthday = new Date();
        Pig pig = new Pig("小猪佩奇",birthday);
        Pig pig1 = (Pig)pig.clone();
        System.out.println("normal"+pig);
        System.out.println("clonable"+pig1);
        *//**
         *  结果（虽然内容一样，但是却不是一个对象）
         *  Pig{namme='小猪佩奇', birthday=Sat Dec 07 13:37:11 CST 2019}prototype.clone.Pig@7f31245a
         *  Pig{namme='小猪佩奇', birthday=Sat Dec 07 13:37:11 CST 2019}prototype.clone.Pig@6d6f6e28
         **//*

        pig.getBirthday().setTime(666666666L);  //get 再 set 就相当于 改原本那个对象 ，改了原本那个对象，那么引用这个对象 的所有对象里面的成员变量都会改变
        pig.setBirthday(new Date());    // 这里的set 其实就是 新new 了一个对象，然后把原来那个对象给占了。
        System.out.println("normal"+pig);
        System.out.println("clonable"+pig1);
        *//**
         * 注意这里 "set 的生日" 是 先get 再set 的。 结果 ： 如果set pig1里面的生日，那么 pig 对象里的生日会跟着变
         * 如果这里 "set 的生日" 是直接 set 对象的成员变量，那么是不会影响其他的。
         **//*

        // 结论： pig 和 pig1 不是一个对象， 但是他们的成员变量 pig.birthday 是一个对象。
        // 如果不想被克隆对象 和 克隆对象 的成员变量都是一个引用类型，那么 就是深拷贝了，要指定具体的成员变量

    }*/

    // 原型模式 和 单例模式的结合
    // 用原型模式来破坏单例模式（原因：clone()方法返回）
    public static void main(String[] args) throws NoSuchMethodException, InvocationTargetException, IllegalAccessException {
        HungrySingleton hungrySingleton = HungrySingleton.getInstance();
        Method method = hungrySingleton.getClass().getDeclaredMethod("clone");
        method.setAccessible(true);

        //映射hungrySingleton 这个对象
        // 因为HungrySingleton 类中clone()方法 返回的是return getInstance(); 而这里又是依据method方法去映射hungrySingleton，所以对象肯定是一个对象。
        HungrySingleton hungrySingletonClone = (HungrySingleton) method.invoke(hungrySingleton);
        System.out.println(hungrySingleton);
        System.out.println(hungrySingletonClone);

    }
}
